/*********************************************
    
   Filname : "sensor_amp.c"

   Driver for Analog Devices Sensor Amplifier AD8555
   The prototypes is defined in the header "sensor_amp.h".
      
   STK500 setup :
   
   CodeVisionAVR C Compiler
   Chip: ATMega16
   
   Henning Hargaard 24/8 2006
**********************************************/

#include <mega16.h>
#include "sensor_amp.h"  

// Bit addressable I/O
#define DIGIN PORTA.2

// Constants
#define SIMULATE_PARAMETER_VALUE 0b00000001
#define SECOND_STAGE_GAIN_CODE   0b00000000
#define FIRST_STAGE_GAIN_CODE    0b00000001
#define OUTPUT_OFFSET_CODE       0b00000010

static void sendData(unsigned char data){
unsigned char i;

  #asm("cli")
  // Set pin DIGIN high
  DIGIN = 1;
  // If data = 0: Pulse width must be between 50 ns and 10 us
  if (data != 0)
  {
    // If data = 1: Minimum 50uS delay (3 cycles per loop at 8 MHz)
    for (i=0; i<133; i++)
    {}
  }
  // Set pin DIGIN low
  DIGIN = 0;
  #asm("sei")
  // Minimum 10uS delay between pulses (3 cycles per loop at 8 MHz)
  for (i=0; i<26; i++)
  {}
}

static void startOfPacket(){
unsigned char i;

  // Send Field 1 (12-Bit Start of Packet 1000 0000 0001)
  sendData(1);
  for (i=0; i<10; i++)
    sendData(0);
  sendData(1);
}

static void endOfPacket(){
unsigned char i;

  // Send Field 5 (12-Bit End of Packet 0111 1111 1110)
  sendData(0);
  for (i=0; i<10; i++)
    sendData(1);
  sendData(0);
}  

static void sendSensorCommand(unsigned char field_1, unsigned char field_2, unsigned char field_4)
{
unsigned char i;
unsigned char mask;
unsigned char tmp;

  // Send Field 0 (Start of Packet)
  startOfPacket();
  
  // Send Field 1 (2 bit command)
  sendData(field_1 & 0b00000010); 
  sendData(field_1 & 0b00000001);
  
  // Send Field 2 (2 bit command)
  sendData(field_2 & 0b00000010); 
  sendData(field_2 & 0b00000001);
  
  // Send Field 3 (2-Bit Dummy 10)
  sendData(1);
  sendData(0);
  
  // Send Field 4 (8-Bit Value)
  mask = 0b10000000;
  tmp = field_4;
  for (i=0; i<8; i++)
  {
    sendData(tmp & mask);
    mask>>=1;
  }

  // Send Field 5 (End of Packet)
  endOfPacket();
}  
  
void sensorInit(){
  // Prepare pin DIGIN (output from Mega16, starting low) 
  DIGIN = 0;
  DDRA.2 = 1;
}

// 0 => 4,00; 127 => 6,40;
void setFirstStageGain(unsigned char gain){
  sendSensorCommand(SIMULATE_PARAMETER_VALUE, FIRST_STAGE_GAIN_CODE, (gain & 0x7F));
}

// 0 => 17,5; 7 => 200;
void setSecondStageGain(unsigned char gain){
  sendSensorCommand(SIMULATE_PARAMETER_VALUE, SECOND_STAGE_GAIN_CODE, (gain & 0x07));
}
 
// 0 => 0 volt; 255 => 5 volt;
void setOutputOffset(unsigned char offset){
  sendSensorCommand(SIMULATE_PARAMETER_VALUE, OUTPUT_OFFSET_CODE, offset);
}
